TweenManager = BaseClass:Extend()
TweenType = {
    POS = "POS",
    LOCAL_POS = "LOCAL_POS",
    POS_X = "POSX",
    POS_Y = "POSY",
    ALPHA = "ALPHA",
    SCALE = "SCALE",
}
local insert = table.insert
local curr_tween_id = -1
function TweenManager:New()
    local o = TweenManager.super.New(self)
    o:Init()
    return o
end

function TweenManager:GetInstance()
    if self.instance == nil then
        self.instance = self:New()
    end
    return self.instance
end

function TweenManager:Init(  )
    self.tween_list = {}
    UpdateBeatManager:GetInstance():AddUpdateBeat(self)
end

--[[args = {
ani_parent = 动画的组件
t_type = 动画类型TweenType
start = 起始值
target = 目标值
time = 持续时间
call_back = 回调
motion_type = 缓动类型
loop = 是否循环
}

--]]
function TweenManager:AddTween (that, args)
    local ani_parent, t_type, start, target, time, call_back, motion_type, loop =
    args.ani_parent, args.t_type, args.start, args.target, args.time, args.call_back, args.motion_type, args.loop
    local _start = false
    local parms = false
    local vo = false
    if t_type == TweenType.POS_X then
        _start = ani_parent.transform.anchoredPosition.x
    elseif t_type == TweenType.POS_Y then
        _start = ani_parent.transform.anchoredPosition.y
    elseif t_type == TweenType.POS then
        _start = ani_parent.transform.anchoredPosition
    elseif t_type == TweenType.SCALE then
        _start = ani_parent.transform.localScale
    elseif t_type == TweenType.LOCAL_POS then
        _start = ani_parent.transform.localPosition
    elseif t_type == TweenType.ALPHA then
        local cg = ani_parent.gameObject:GetComponent(typeof(CSE.CanvasGroup))
        if not IsNull(cg) then
            parms = cg
        else
            parms = ani_parent.gameObject:AddComponent(typeof(CSE.CanvasGroup))
        end
        _start = parms.alpha
    end
    curr_tween_id = curr_tween_id + 1
    self.tween_list[curr_tween_id] = {
        ani_parent = ani_parent,
        t_type = t_type,
        start = start or _start,
        target = target,
        time = time,
        call_back = call_back,
        motion_type = motion_type,
        loop = loop,
        currTime = 0,
        parms = parms
    }
    return curr_tween_id
end

function TweenManager:Update (time,deltaTime)
    for i, v in pairs(self.tween_list) do
        if v then
            if v.currTime + deltaTime <= v.time then
                v.currTime = v.currTime + deltaTime
                local progress = self:GetProgress(v)
                self:HandlerTweenVO(v,progress)
            else
                --循环逻辑
                if v.loop then
                    v.currTime = 0
                    local progress = self:GetProgress(v)
                    self:HandlerTweenVO(v,progress)
                else
                    self.tween_list[i] = nil
                    if v.call_back then
                        v.call_back()
                    end
                end
            end
        end
    end
end

function TweenManager:GetProgress (vo)
    local progress = math.min(vo.currTime / vo.time,1)
    progress = self:GetMotion(vo.motion_type , progress)
    return progress
end

function TweenManager:GetMotion (motion_type,progress)
    if type(motion_type) == "function" and motion_type then
        return motion_type(progress)
    end
    if type(motion_type) == "string" and motion_type then
        return TweenMotion[motion_type](progress)
    end
    return 1
end

function TweenManager:HandlerTweenVO (vo,progress)
    local parent = vo.ani_parent
    local curr = vo.start + (vo.target - vo.start) * progress
    if vo.t_type == TweenType.POS_X then
        local vect = Vector2(curr,parent.anchoredPosition.x)
        parent.anchoredPosition = vect
    elseif vo.t_type == TweenType.POS_Y then
        local vect = Vector2(curr,parent.anchoredPosition.y)
        parent.anchoredPosition = vect
    elseif vo.t_type == TweenType.POS then
        parent.transform.anchoredPosition = curr
    elseif vo.t_type == TweenType.SCALE then
        parent.transform.localScale = curr
    elseif vo.t_type == TweenType.ALPHA then
        local cg = vo.parms
        cg.alpha = curr
    elseif vo.t_type == TweenType.LOCAL_POS then
        parent.transform.localPosition = curr
    end
end

function TweenManager:RemoveTween (id)
    self.tween_list[id] = nil
end